.model small

public printString
public drawCrossRoad
public updateSemaphore
public updatePedSemaphore
public horiz_pos
public vert_pos

	getArg macro reg, x
	mov reg, [bp + 4 + 2*x]
	endm

	setArg macro reg, x
	mov [bp + 4 + 2*x], reg
	endm

DATA segment 
		simulator db "Simulacija saobracajne raskrsnice$"
		startSim db "s - startujte simulaciju$"
		pauseSim db "p - pauzirajte simulaciju $"
		addCar db "u - dodajte automobil$"
		endSim db "Esc - kraj simulacije.$"
		
		; koordinate za pozicije semafora automobila
		
		EastRight equ 2744d
		EastStr equ 2424d
		EastLeft equ 2104d
		
		WestRight equ 1184d
		WestStr equ 1504d
		WestLeft equ 1824d
		
		SouthRight equ 3086d
		SouthStr equ 3092d
		SouthLeft equ 3098d
		
		NorthRight equ 828d
		NorthStr equ 834d
		NorthLeft equ 840d
		
		; koordinate i char za pozicije semafora peshaka
		
		Horiz_1	equ 660d
		Horiz_2 equ 704d
		Horiz_3	equ 3220d
		Horiz_4	equ 3264d
		HorizLight equ 219 
		 
		Vert_1	equ 816d
		Vert_2	equ 868d
		Vert_3	equ 3056d
		Vert_4	equ 3108d
		VertLight equ 219 
		
		; boje
		
		c_red equ 100b 
		c_yellow equ 1110b
		c_green equ 010b
		c_off equ 111b ;sivo
		
		horiz_pos equ 0
		vert_pos equ 1
		
DATA ends
.stack 
.code

firstLineType proc near
	push bp
	mov bp, sp

	push ax
	push bx
	push dx
	push di
	push es
	push cx
	
	mov ax, 0b800h
	mov es, ax	
	
	
	mov ah, 033h
	mov al, "" 
	
	
	getArg di 0
	
	mov cx, 12	
	cld 		
	rep stosw 	

		
	mov ah, 1111b
	mov al, 221
	
	mov cx, 1 
	cld 		
	rep stosw 	

	
	
	
	mov ah, 0000b
	mov al, ""
	
	mov cx, 2 	
	cld 		
	rep stosw 	

	

	
	mov ah, 1111b
	mov al, "|"
	
	mov cx, 1 	
	cld 		
	rep stosw 	

	
	mov ah, 0000b
	mov al, ""
	
	mov cx, 2 
	cld 		
	rep stosw 	
	
	
	
	mov ah, 1111b
	mov al, "|"
	
	mov cx, 1 
	cld 		
	rep stosw 	
	
	;mov es:byte ptr[di], al
	;mov es:byte ptr[di+1], ah
    
	mov ah, 0000b
	mov al, ""
	
	mov cx, 2 	; amount of times to put it there 
	cld 		; direction - forwards
	rep stosw 	; output character at ES:[DI]
	
	;mov es:byte ptr[di], al
	;mov es:byte ptr[di+1], ah

	 
	mov ah, 1111b
	mov al, 221

	mov cx, 1 	; amount of times to put it there 
	cld 		; direction - forwards
	rep stosw 	; output character at ES:[DI]
	
;	mov es:byte ptr[di], al
;	mov es:byte ptr[di+1], ah
	
	mov ah, 0000b
	mov al, ""
	
	;mov es:byte ptr[di], al
	;mov es:byte ptr[di+1], ah
	
	mov cx, 2 	; amount of times to put it there 
	cld 		; direction - forwards
	rep stosw 	; output character at ES:[DI]
	
	mov ah, 1111b
	mov al, "|"
	
	;mov es:byte ptr[di], al
	;mov es:byte ptr[di+1], ah
	
	mov cx, 1 	; amount of times to put it there 
	cld 		; direction - forwards
	rep stosw 	; output character at ES:[DI]
	
	mov ah, 0000b
	mov al, ""
	
	;mov es:byte ptr[di], al
	;mov es:byte ptr[di+1], ah
	
	mov cx, 2 	; amount of times to put it there 
	cld 		; direction - forwards
	rep stosw 	; output character at ES:[DI]
	
	mov ah, 1111b
	mov al, "|"
	
	mov cx, 1 	; amount of times to put it there 
	cld 		; direction - forwards
	rep stosw 	; output character at ES:[DI]
	
    
	mov ah, 0000b
	mov al, ""
	
	mov cx, 2 	
	cld 		; direction - forwards
	rep stosw 	; output character at ES:[DI]
	
	 
	mov ah, 1111b
	mov al, 222
	
	mov cx, 1 	
	cld 		
	rep stosw 	
	
	mov ah, 033h
	mov al, "" 	
	
	
	mov cx, 12 	
	cld 		
	rep stosw 	

	mov ah, 00h
	mov al, "" 	
	
	
	mov cx, 37 	
    cld 		
	rep stosw 	
	
	setArg di 0
	
	pop cx
	pop es
	pop di
	pop dx
	pop bx 
	pop ax
	pop bp
	ret  
firstLineType endp

secondLineType proc near
	push bp
	mov bp, sp

	push ax
	push bx
	push dx
	push di
	push es
	
	mov ax, 0b800h
	mov es, ax	; VIDEO mode
	
	getArg di 0
	
	mov ah, 1111b
	mov al, 223 	
	
	
	mov cx, 12 	 
	cld 		
	rep stosw 	
	
	
	mov ah, 00h
	mov al, "" 	
	
	
	mov cx, 19 	 
	cld 		
	rep stosw 	
	
	
	
	mov ah, 1111b
	mov al, 223 	
	
	
	mov cx, 12	 
	cld 		
	rep stosw 
	
		;add di, 37
	
	mov ah, 00h
	mov al, "" 	; character to put there
	
	
	mov cx, 37 	; amount of times to put it there 
    cld 		; direction - forwards
	rep stosw 	; output character at ES:[DI]

	
	setArg di 0
	
	pop es
	pop di
	pop dx
	pop bx 
	pop ax
	pop bp
	ret
secondLineType endp

thirdLineType proc near
	push bp
	mov bp, sp

	push ax
	push bx
	push dx
	push di
	push es
	
	mov ax, 0b800h
	mov es, ax	; VIDEO mode
	
	getArg di 0
	
;	add di, 80
	mov ah, 00h
	mov al, "" 	
	
	mov cx, 80	 
	cld 		
	rep stosw 	
	
	setArg di 0
	
	
	pop es
	pop di
	pop dx
	pop bx 
	pop ax
	pop bp
	ret
thirdLineType endp

fourthLineType proc near
	push bp
	mov bp, sp

	push ax
	push bx
	push dx
	push di
	push es
	
	mov ax, 0b800h
	mov es, ax	; VIDEO mode
	
	getArg di 0
	
	mov ah, 1111b
	mov al, "-" 	
	
	
	mov cx, 12 	 
	cld 		
	rep stosw 	
	
	
	mov ah, 00h
	mov al, "" 	
	
	
	mov cx, 19 	 
	cld 		
	rep stosw 	
	
	
	
	mov ah, 1111b
	mov al, "-" 	
	
	
	mov cx, 12	 
	cld 		
	rep stosw 
	
	
	
	mov ah, 00h
	mov al, "" 	; character to put there
	
	
	mov cx, 37 	; amount of times to put it there 
    cld 		; direction - forwards
	rep stosw 	; output character at ES:[DI]
	
	setArg di 0
	
	pop es
	pop di
	pop dx
	pop bx 
	pop ax
	pop bp
	ret
fourthLineType endp

fifthLineType proc near
	push bp
	mov bp, sp

	push ax
	push bx
	push dx
	push di
	push es
	
	mov ax, 0b800h
	mov es, ax	; VIDEO mode
	
	getArg di 0
	
	mov ah, 1111b
	mov al, 220 	
	
	
	mov cx, 12 	 
	cld 		
	rep stosw 	
	
	
	mov ah, 00h
	mov al, "" 	
	
	
	mov cx, 19 	 
	cld 		
	rep stosw 	
	
	
	
	mov ah, 1111b
	mov al, 220 	
	
	
	mov cx, 12	 
	cld 		
	rep stosw 
	
		;add di, 37
	
	mov ah, 00h
	mov al, "" 	; character to put there
	
	
	mov cx, 37 	; amount of times to put it there 
    cld 		; direction - forwards
	rep stosw 	; output character at ES:[DI]

	
	setArg di 0
	
	pop es
	pop di
	pop dx
	pop bx 
	pop ax
	pop bp
	ret
fifthLineType endp

setCursorPos proc near ; nije potrebna jer se vec postavi u di
	push ax
	push bx
	
	mov ah, 2
	mov bh, 0
	int 10h
	
	pop bx
	pop ax
	ret
setCursorPos endp

printString proc near
	push bp
	mov bp, sp
	
	push ax
	push es
	push bx
	push di
	push si
	push dx
	
	mov ax, 0b800h
	mov es, ax ; VIDEO MODE
	
	;mov ax, 2
	;int 10h
	
	getArg di 0 ; koordinate
	getArg bx, 1 ; pocetak stringa
	
	mov si, bx
	xor ax, ax
moreCha:
	mov al, [si]
	cmp ax, '$'
	je endString 
	mov es: byte ptr [di], al
	mov es: byte ptr [di+1], 1111b
	inc si
	inc di
	inc di
	jmp moreCha
	
endString:	
	pop dx 
	pop si
	pop di
	pop bx
	pop es
	pop ax
	pop bp
	ret
printString endp

drawCrossRoad proc near
	push bp
	mov bp, sp
	
	push ax
	push es
	push di
	push cx
	
	mov ax, 0b800h
	mov es, ax ; VIDEO MODE

	xor di,di 
	
	
	mov cx, 6
top:
	push di
	call firstLineType
	pop di
	loop top
	
	push di
	call secondLineType
	pop di
	
	push di
	call thirdLineType
	pop di

	push di
	call fourthLineType
	pop di
	
	push di
	call thirdLineType
	pop di

	push di
	call fourthLineType
	pop di
	
	push di
	call thirdLineType
	pop di
	
	
	push di
	call fifthLineType
	pop di
	
	push di
	call thirdLineType
	pop di

	push di
	call fourthLineType
	pop di
	
	push di
	call thirdLineType
	pop di

	push di
	call fourthLineType
	pop di
	
	push di
	call thirdLineType
	pop di
	
	push di
	call fifthLineType
	pop di
	
	mov cx, 6
bottom:
		push di
		call firstLineType
		pop di
		loop bottom
	
		 
	lea bx, simulator
	mov di, 250d
	push bx
	push di
	call printString
	
	lea bx, startSim
	mov di, 570d
	push bx
	push di
	call printString
	
	lea bx, addCar
	mov di, 730d
	push bx
	push di
	call printString
	
	lea bx, endSim
	mov di, 890d
	push bx
	push di
	call printString

	;inicialno dodavanje semafora za automobile. svi crveni.
	mov di, EastRight
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
	
	mov di, EastStr
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
	
	mov di, EastLeft
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
		
	mov di, WestRight
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
	
	mov di, WestStr
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
	
	mov di, WestLeft
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
	
	mov di, SouthRight
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
	
	mov di, SouthStr
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
	
	mov di, SouthLeft
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
	
	mov di, NorthRight
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
	
	mov di, NorthStr
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
	
	mov di, NorthLeft
	mov es: byte ptr [di], 254
	mov es: byte ptr [di+1], 04h
	
	;inicijalno postavljanje semafora za pesake. svi zeleni.
	
	mov di, Horiz_1
	mov es: byte ptr [di], HorizLight 
	mov es: byte ptr [di+1], c_green
	
	mov di, Horiz_2
	mov es: byte ptr [di], HorizLight
	mov es: byte ptr [di+1], c_green
	
	mov di, Horiz_3
	mov es: byte ptr [di], HorizLight
	mov es: byte ptr [di+1], c_green
	
	mov di, Horiz_4
	mov es: byte ptr [di], HorizLight
	mov es: byte ptr [di+1], c_green
	
	mov di, Vert_1
	mov es: byte ptr [di], VertLight
	mov es: byte ptr [di+1], c_green
	
	mov di, Vert_2
	mov es: byte ptr [di], VertLight
	mov es: byte ptr [di+1], c_green
	
	mov di, Vert_3
	mov es: byte ptr [di], VertLight
	mov es: byte ptr [di+1], c_green
	
	mov di, Vert_4
	mov es: byte ptr [di], VertLight
	mov es: byte ptr [di+1], c_green
	
	pop cx
	pop di
	pop es
	pop ax
	pop bp
	ret

drawCrossRoad endp



;----------------------------------------------------
; signature:	void updateSemaphore(Side, Order, Light)
;				>	Side		-	south, east, north, west (0, 1, 2, 3)
;				>	Order		-	left, foreward, right (0, 1, 2)
;				>	Light		-	light to set
; description:	sets the semaphore light
; comment:		the arguments are passed through the stack;
;				frees the arguments on the stack

updateSemaphore proc near
	push bp
	mov bp, sp
	
	push ax
	push dx
	push di
	push bx
	
	mov ax, 0b800h
	mov es, ax ; VIDEO MODE

	getArg bx, 0 ; light
	getArg ax, 1 ; order
	getArg dx, 2 ; side
	
	cmp ax, 0
	je sth
	cmp ax, 1
	je est
	cmp ax, 2
	je nrth
	cmp ax, 3
	je wst
	
sth: cmp dx, 0
	 je sl
	 cmp dx, 1
	 je sf
	 cmp dx, 2
	 je sr
	 
nrth: cmp dx, 0
	 je nl
	 cmp dx, 1
	 je nf
	 cmp dx, 2
	 je nr

est: cmp dx, 0
	 je el
	 cmp dx, 1
	 je ef
	 cmp dx, 2
	 je er
wst: cmp dx, 0
	 je wl
	 cmp dx, 1
	 je wf
	 cmp dx, 2
	 je wr

sl: mov di, SouthLeft
	jmp cont
sf: mov di, SouthStr
	jmp cont
sr: mov di, SouthRight
	jmp cont

nl: mov di, NorthLeft
	jmp cont
nf: mov di, NorthStr
	jmp cont
nr: mov di, NorthRight
	jmp cont

el: mov di, EastLeft
	jmp cont
ef: mov di, EastStr
	jmp cont
er: mov di, EastRight
	jmp cont

wl: mov di, WestLeft
	jmp cont
wf: mov di, WestStr
	jmp cont
wr: mov di, WestRight
	jmp cont

cont:
	xor ax, ax
	cmp bx, 0
	je coff
	cmp bx, 1
	je cred
	cmp bx, 2
	je cyell
	cmp bx, 3
	je cgreen

coff: mov al, c_off
	  jmp setsem
cred: mov al, c_red
	  jmp setsem
cyell: mov al, c_yellow
	  jmp setsem
cgreen: mov al, c_green
	  jmp setsem
	  
setsem:
		mov es: byte ptr[di], 254
		mov es: byte ptr[di+1], al
	
	
	pop bx
	pop di
	pop dx
	pop ax
	pop bp
	ret	
updateSemaphore endp

;----------------------------------------------------
; signature:	void updatePedSemaphore(Position, Light)
;				>	Position		-	horizontal, vertical (0, 1)
;				>	Light		-	light to set
; description:	sets the pedestrian semaphore light
; comment:		the arguments are passed through the stack;
;				frees the arguments on the stack


updatePedSemaphore proc near
	push bp
	mov bp, sp
	
	push ax
	push dx
	push di
	push bx
	
	mov ax, 0b800h
	mov es, ax ; VIDEO MODE

	getArg ax 0 ; position
	mov dx, ax
	getArg bx 1 ; light

	xor ax, ax
	cmp bx, 0
	je coff_h
	cmp bx, 1
	je cred_h
	cmp bx, 2
	je cyell_h
	cmp bx, 3
	je cgreen_h
	
coff_h: mov al, c_off
	  jmp dissem
cred_h: mov al, c_red
	  jmp dissem
cyell_h: mov al, c_yellow
	  jmp dissem
cgreen_h: mov al, c_green
	  jmp dissem
	  
dissem:	
	cmp dx, 0
	je Hor
	cmp dx, 1
	je Ver
	
Hor:
	mov di, Horiz_1
	mov es: byte ptr [di], HorizLight 
	mov es: byte ptr [di+1], al
	
	mov di, Horiz_2
	mov es: byte ptr [di], HorizLight
	mov es: byte ptr [di+1], al
	
	mov di, Horiz_3
	mov es: byte ptr [di], HorizLight
	mov es: byte ptr [di+1], al
	
	mov di, Horiz_4
	mov es: byte ptr [di], HorizLight
	mov es: byte ptr [di+1], al
	jmp end_setps

Ver:
	mov di, Vert_1
	mov es: byte ptr [di], VertLight
	mov es: byte ptr [di+1], al
	
	mov di, Vert_2
	mov es: byte ptr [di], VertLight
	mov es: byte ptr [di+1], al
	
	mov di, Vert_3
	mov es: byte ptr [di], VertLight
	mov es: byte ptr [di+1], al
	
	mov di, Vert_4
	mov es: byte ptr [di], VertLight
	mov es: byte ptr [di+1], al
	jmp end_setps

end_setps:
		pop bx
		pop di
		pop dx
		pop ax
		pop bp
		ret	
	
updatePedSemaphore endp

main proc	
	
	mov ax, DATA
    mov ds, ax
	
	mov ax,0B800h 	; segment of video buffer
	mov es,ax 	; put this into es
	
	mov ax, 2 ; ukljucivanje video memorije 
	int 10h
	
	;brisanje ekrana
	
	xor di,di 	
	xor ax, ax
	mov cx,2000d 	
	cld 		; funkcije koje cx puta ispisuju ax simbol i di se koristi za iteraciju i di se menja. ispisuje se u video memoriju na koju 
	rep stosw 	; ukazuje es
	
	call drawCrossRoad
	
	mov bx, 2
	mov ax, 1
	mov di, 2
	
	push di
	push ax
	push bx
	call updateSemaphore
	
	mov bx, 0
	mov ax, 3
	mov di, 3
	
	push di
	push ax
	push bx
	call updateSemaphore
	
	mov ax, 1
	mov bx, 2
	push bx
	push ax
	call updatePedSemaphore
	
	sti
	xor ax, ax
	mov ax,04C00h 	; return to DOS
	int 21h
main endp
end main